#include "boxman.h"

QBoxMan::QBoxMan(int Index)
{
    //加载当前关卡数
    levelIndex = Index;
    //实例化地图对象
    DataConfig config;
    //导入地图数据
    for(int i=0; i<M_TAB_WIDTH; i++)
    {
        for(int j=0; j<M_TAB_HEIGTHT; j++)
        {
            m_Map[i][j] = config.mData[this->levelIndex][i][j];
        }
    }
    //寻找当前人的位置
    for(int i=0; i<M_TAB_WIDTH; i++)
    {
        for(int j=0;j<M_TAB_HEIGTHT; j++)
        {
            if(m_Map[i][j] == MAP_MAN_WAY || m_Map[i][j] == MAP_MAN_DESTINY)
            {
                man_x = i;
                man_y = j;
            }
        }
    }
}

void QBoxMan::drawMap(QPainter *pDraw)
{
    //加载图片的路径
    QString pathURL;
    for(int i=0; i<M_TAB_WIDTH; i++)
    {
        for(int j=0; j<M_TAB_HEIGTHT; j++)
        {
            switch (m_Map[i][j])
            {
            case MAP_BACKGROUND:
                pathURL = ":/res/s1.png";
                break;
            case MAP_WAY:
                pathURL = ":/res/s3.png";
                break;
            case MAP_WALL:
                pathURL = ":/res/s2.png";
                break;
            case MAP_DESTINY:
                pathURL = ":/res/s6.png";
                break;
            case MAP_MAN_WAY:
                pathURL = ":/res/s5.png";
                break;
            case MAP_MAN_DESTINY:
                pathURL = ":/res/s5.png";
                break;
            case MAP_BOX:
                pathURL = ":/res/s4.png";
                break;
            case MAP_BOX_FIXED:
                pathURL = ":/res/s4.png";
                break;
            }
            QPixmap pix;
            pix.load(pathURL);
            pix = pix.scaled(pix.width(),pix.height());
            pDraw->drawPixmap(QRect(j*pix.width(),i*pix.height(),pix.width(),pix.height()),pix);
        }
    }
}

void QBoxMan::keyDown(QKeyEvent *event)
{
    //分别表示不同键盘事件下
    //下一个移动位置和可能影响到的第二个位置
    int x_0 = man_x;
    int y_0 = man_y;
    int x_1;
    int y_1;
    int x_2;
    int y_2;

    switch (event->key())
    {
    //键盘事件为向上
    case Qt::Key_A:
    case Qt::Key_Left:
        x_1 = man_x;
        y_1 = man_y - 1;
        x_2 = man_x;
        y_2 = man_y - 2;
        break;

    //键盘事件为向下
    case Qt::Key_D:
    case Qt::Key_Right:
        x_1 = man_x;
        y_1 = man_y + 1;
        x_2 = man_x;
        y_2 = man_y + 2;
        break;

    //键盘事件为向左
    case Qt::Key_W:
    case Qt::Key_Up:
        x_1 = man_x - 1;
        y_1 = man_y;
        x_2 = man_x - 2;
        y_2 = man_y;
        break;

    //键盘事件为向右
    case Qt::Key_S:
    case Qt::Key_Down:
        x_1 = man_x + 1;
        y_1 = man_y;
        x_2 = man_x + 2;
        y_2 = man_y;
        break;


    default:
        return;
    }

    update(x_0, y_0, x_1, y_1, x_2, y_2);
}

void QBoxMan::update(int x_0, int y_0, int x_1, int y_1, int x_2, int y_2)
{
    switch (m_Map[x_1][y_1])
    {
    //前方是墙 不做任何事
    case MAP_WALL:
        break;

    //前方是路
    case MAP_WAY:
        //人向前走一步
        m_Map[x_1][y_1] = MAP_MAN_WAY;
        man_x = x_1;
        man_y = y_1;
        //回顾来时位置的状态
        if(m_Map[x_0][y_0] == MAP_MAN_WAY)
        {
            //来时不在目的点
            m_Map[x_0][y_0] = MAP_WAY;
            break;
        }
        if(m_Map[x_0][y_0] == MAP_MAN_DESTINY)
        {
            //来时在目的点 还原
            m_Map[x_0][y_0] = MAP_DESTINY;
            break;
        }
        //若地图没有错误，应当没有其他情况

    //前方是目的点
    case MAP_DESTINY:
        //人向前走一步
        m_Map[x_1][y_1] = MAP_MAN_DESTINY;
        man_x = x_1;
        man_y = y_1;
        //回顾来时位置的状态
        if(m_Map[x_0][y_0] == MAP_MAN_WAY)
        {
            //来时不在目的点
            m_Map[x_0][y_0] = MAP_WAY;
            break;
        }
        if(m_Map[x_0][y_0] == MAP_MAN_DESTINY)
        {
            //来时在目的点 还原
            m_Map[x_0][y_0] = MAP_DESTINY;
            break;
        }

    //前方是未放置好的箱子
    case MAP_BOX:
        //第三个位置是过道
        if(m_Map[x_2][y_2] == MAP_WAY)
        {
            //第三个位置改为箱子状态
            m_Map[x_2][y_2] = MAP_BOX;
            //人向前走
            m_Map[x_1][y_1] = MAP_MAN_WAY;
            man_x = x_1;
            man_y = y_1;
            //回顾来时位置的状态
            if(m_Map[x_0][y_0] == MAP_MAN_WAY)
            {
                //来时不在目的点
                m_Map[x_0][y_0] = MAP_WAY;
                break;
            }
            if(m_Map[x_0][y_0] == MAP_MAN_DESTINY)
            {
                //来时在目的点 还原
                m_Map[x_0][y_0] = MAP_DESTINY;
                break;
            }
        }
        //第三个位置为目的点
        if(m_Map[x_2][y_2] == MAP_DESTINY)
        {
            //第三个位置改为放置好的箱子状态
            m_Map[x_2][y_2] = MAP_BOX_FIXED;
            //人向前走
            m_Map[x_1][y_1] = MAP_MAN_WAY;
            man_x = x_1;
            man_y = y_1;
            //回顾来时位置的状态
            if(m_Map[x_0][y_0] == MAP_MAN_WAY)
            {
                //来时不在目的点
                m_Map[x_0][y_0] = MAP_WAY;
                break;
            }
            if(m_Map[x_0][y_0] == MAP_MAN_DESTINY)
            {
                //来时在目的点 还原
                m_Map[x_0][y_0] = MAP_DESTINY;
                break;
            }
        }
        //第三个位置为箱子或墙则不移动
        break;

    //前方为放置好的箱子
    case MAP_BOX_FIXED:
        //第三个位置是过道
        if(m_Map[x_2][y_2] == MAP_WAY)
        {
            //第三个位置改为箱子状态
            m_Map[x_2][y_2] = MAP_BOX;
            //人向前走
            m_Map[x_1][y_1] = MAP_MAN_DESTINY;
            man_x = x_1;
            man_y = y_1;
            //回顾来时位置的状态
            if(m_Map[x_0][y_0] == MAP_MAN_WAY)
            {
                //来时不在目的点
                m_Map[x_0][y_0] = MAP_WAY;
                break;
            }
            if(m_Map[x_0][y_0] == MAP_MAN_DESTINY)
            {
                //来时在目的点 还原
                m_Map[x_0][y_0] = MAP_DESTINY;
                break;
            }
        }
        //第三个位置为目的点
        if(m_Map[x_2][y_2] == MAP_DESTINY)
        {
            //第三个位置改为放置好的箱子状态
            m_Map[x_2][y_2] = MAP_BOX_FIXED;
            //人向前走
            m_Map[x_1][y_1] = MAP_MAN_DESTINY;
            man_x = x_1;
            man_y = y_1;
            //回顾来时位置的状态
            if(m_Map[x_0][y_0] == MAP_MAN_WAY)
            {
                //来时不在目的点
                m_Map[x_0][y_0] = MAP_WAY;
                break;
            }
            if(m_Map[x_0][y_0] == MAP_MAN_DESTINY)
            {
                //来时在目的点 还原
                m_Map[x_0][y_0] = MAP_DESTINY;
                break;
            }
        }
        //第三个位置为箱子或墙则不移动
        break;
    }
}

bool QBoxMan::gameOver()
{
    //判断箱子是否全部归位
    for(int i=0;i<M_TAB_WIDTH;i++)
    {
        for(int j=0;j<M_TAB_HEIGTHT;j++)
        {
            if(m_Map[i][j] == MAP_DESTINY || m_Map[i][j] == MAP_MAN_DESTINY)
            {
                return false;
            }
        }
    }
    return true;
}



